<?php
/**
 * @Author: liuhongbin
 * @Email: 514660094@qq.com
 * @Date: 2019-02-12 16:15:10
 * @Description:
 * @LastEditors: liuhongbin
 * @LastEditTime: xxx
 */

namespace hiduoke\services\wechat\traits;

use app\common\model\wechat\WechatShare;
use app\common\model\wechat\WechatShareReceiver;
use app\common\model\wechat\WechatUser;
use app\common\model\wechat\WechatUserWallet;
use hiduoke\services\facade\WechatService as Ws;
use think\Exception;
use think\facade\Db;
use think\facade\Log;
use EasyWeChat\Factory;
use hiduoke\services\facade\Snowflake;
use app\common\model\wechat\WechatOrder;
use app\common\model\wechat\WechatRefund;
use GuzzleHttp\Exception\GuzzleException;
use app\common\model\wechat\WechatTransfer;
use app\common\model\platform\PlatformSetting;
use EasyWeChat\Kernel\Exceptions\InvalidConfigException;
use EasyWeChat\Kernel\Exceptions\InvalidArgumentException;

trait WechatOrderService
{
    /**
     * @var \EasyWeChat\Payment\Application
     */
    protected $orderApp;

    /**
     * @var \EasyWeChat\Payment\Application
     */
    protected $transferApp;

    /**
     * 支付配置
     * @var array
     */
    protected $orderConfig;
    /**
     * 企付零配置
     * @var array
     */
    protected $transferConfig;

    /**
     * 获取支付配置
     * @return array
     */
    public function getOrderConfig()
    {
        $pay = (new PlatformSetting())->getValueByKey("pay", $this->plaid);
        if (!$pay) {
            return [];
        }
        $config = [
            // 必要配置
            'app_id'     => $this->wechat->appid,
            'mch_id'     => $pay['mch_id'],
            'key'        => $pay['key'],   // API 密钥
            'cert_path'  => app()->getRootPath() . 'cert/' . $pay['pem_cert'][0]['url'],
            'key_path'   => app()->getRootPath() . 'cert/' . $pay['pem_key'][0]['url'],
            'notify_url' => $this->getNotifyUrl(),     // 你也可以在下单时单独设置来想覆盖它
            'log'        => [
                'default'  => 'error', // 默认使用的 channel，生产环境可以改为下面的 prod
                'channels' => [
                    'error' => [
                        'driver' => 'single',
                        'path'   => '/tmp/easywechat/order_account_error.log',
                        'level'  => 'error',
                    ],
                ],
            ],
        ];
        return $config;
    }

    /**
     * 获取企付零配置
     * @return array
     */
    public function getTransferConfig()
    {
        $transfer = (new PlatformSetting())->getValueByKey("transfer", $this->plaid);
        if ($transfer['state']) {
            $config = [
                // 必要配置
                'app_id'     => $this->wechat->appid, //这里是同一个公众号的才行
                'mch_id'     => $transfer['mch_id'],
                'key'        => $transfer['key'],   // API 密钥
                'cert_path'  => app()->getRootPath() . 'cert/' . $transfer['pem_cert'][0]['url'],
                'key_path'   => app()->getRootPath() . 'cert/' . $transfer['pem_key'][0]['url'],
                'notify_url' => $this->getNotifyUrl(),     // 你也可以在下单时单独设置来想覆盖它
                'log'        => [
                    'default'  => 'error', // 默认使用的 channel，生产环境可以改为下面的 prod
                    'channels' => [
                        'error' => [
                            'driver' => 'single',
                            'path'   => '/tmp/easywechat/transfer_account_error.log',
                            'level'  => 'error',
                        ],
                    ],
                ],
            ];
            return $config;
        } else {
            return $this->getOrderConfig();
        }
    }

    /**
     * 支付handler
     * @param array $orderConfig
     * @return \EasyWeChat\Payment\Application
     */
    public function getOrderApp($orderConfig = [])
    {
        if ($this->orderApp) {
            return $this->orderApp;
        } else {
            if ($orderConfig) {
                $this->orderConfig = $orderConfig;
            } else {
                $this->orderConfig = $this->getOrderConfig();
            }
            $this->orderApp = Factory::payment($this->orderConfig);
            return $this->orderApp;
        }
    }

    /**
     * @param array $payConfig
     * @return \EasyWeChat\Payment\Order\Client
     */
    public function getOrder($payConfig = [])
    {
        return $this->getOrderApp($payConfig)->order;
    }

    /**
     * 分账
     * @param array $payConfig
     * @return \EasyWeChat\Payment\ProfitSharing\Client
     */
    public function getProfitSharing($payConfig = [])
    {
        return $this->getOrderApp($payConfig)->profit_sharing;
    }

    /**
     * 企付零handler
     * @param array $transferConfig
     * @return \EasyWeChat\Payment\Application
     */
    public function getTransferApp($transferConfig = [])
    {
        if ($this->transferApp) {
            return $this->transferApp;
        } else {
            if ($transferConfig) {
                $this->transferConfig = $transferConfig;
            } else {
                $this->transferConfig = $this->getTransferConfig();
            }
            $this->transferApp = Factory::payment($this->transferConfig);
            return $this->transferApp;
        }
    }

    /**
     * @param array $transferConfig
     * @return \EasyWeChat\Payment\Transfer\Client
     */
    public function getTransfer($transferConfig = [])
    {
        return $this->getTransferApp($transferConfig)->transfer;
    }

    /**
     * 企付零
     * @param string $money
     * @param string $desc
     * @param string $openid
     * @param string $partner_trade_no
     * @param string $check_name
     * @param string $re_user_name
     * @return array|\EasyWeChat\Kernel\Support\Collection|object|\Psr\Http\Message\ResponseInterface|string
     * @throws Exception
     */
    public function transfer(string $money, $desc = '', string $openid = '', string $partner_trade_no = '', $check_name = 'NO_CHECK', $re_user_name = '')
    {
        $amount = intval($money * 100);
        if ($amount <= 0) {
            throw new Exception('金额不存在或者参数不正确');
        }

        $openid = $openid ?: $this->getOpenid();
        if (!$openid) {
            throw new Exception('openid不存在');
        }
        $config = (new PlatformSetting())->getValueByKey("transfer", $this->plaid);

        $desc = ($desc ?: $config['desc']) ?: '红包';

        $partner_trade_no = $partner_trade_no ?: $this->getSnowflakeNumber("FK");

        try {
            $result = $this->getTransfer()->toBalance([
                'partner_trade_no' => $partner_trade_no, // 商户订单号，需保持唯一性(只能是字母或者数字，不能包含有符号)
                'openid'           => $openid,
                'check_name'       => $check_name, // NO_CHECK：不校验真实姓名, FORCE_CHECK：强校验真实姓名
                're_user_name'     => $re_user_name, // 如果 check_name 设置为FORCE_CHECK，则必填用户真实姓名
                'amount'           => $amount, // 企业付款金额，单位为分
                'desc'             => $desc, // 企业付款操作说明信息。必填
            ]);
        } catch (InvalidArgumentException $e) {
        } catch (InvalidConfigException $e) {
        } catch (GuzzleException $e) {
        } catch (\Exception $e) {
            Log::error($e->getMessage() . '出错行' . $e->getLine());
            return ['return_code' => 'FAIL', 'result_code' => 'FAIL', 'return_msg' => $e->getMessage()];
        }
        if ($this->checkResult($result)) {
            $data = array(
                'partner_trade_no' => $partner_trade_no,
                'payment_no'       => $result['payment_no'],
                'openid'           => $openid,
                'amount'           => $amount,
                'desc'             => $desc,
                'plaid'            => $this->plaid,
                'addon'            => $this->addon_name
            );
            (new WechatTransfer())->save($data);
        }
        return $result;
    }

    /**
     * 企付零自动
     * @param string $money
     * @param string $desc
     * @param string $openid
     * @param string $partner_trade_no
     * @param string $check_name
     * @param string $re_user_name
     * @return array|\EasyWeChat\Kernel\Support\Collection|object|\Psr\Http\Message\ResponseInterface|string|\think\Model
     * @throws Exception
     */
    public function transferAuto(string $money, $desc = '', string $openid = '', string $partner_trade_no = '', $check_name = 'NO_CHECK', $re_user_name = '')
    {
        $openid = $openid ?: $this->getOpenid();
        $config = (new PlatformSetting())->getValueByKey("transfer", $this->plaid);
        $pay_time = $config['pay_time'];//付款次数
        $day_pay_time = (new WechatTransfer())->getTodayCount($openid);
        if ($pay_time > $day_pay_time) {
            //企付零
            return $this->transfer($money, $desc, $openid, $partner_trade_no, $check_name, $re_user_name);
        } else {
            //余额
            $user_id = (new WechatUser())->where(['openid' => $openid])->value('id');
            return (new WechatUserWallet())->changeMoney($money, '自动打款次数超出', 0, $user_id);
        }
    }

    /**
     * 订单
     * @param string $money 下单金额
     * @param string $body 订单名称
     * @param string $openid 用户openid 默认为当前用户
     * @param string $out_trade_no 商户订单号
     * @return array|string
     */
    public function order(string $money, $body = '', $profit_sharing = "N", string $openid = '', $out_trade_no = '', $attach = '', $trade_type = 'JSAPI')
    {
        $total_fee = intval($money * 100);
        if (!$total_fee || $total_fee <= 0) {
            throw new Exception('金额不存在或者参数不正确');
        }
        $openid = $openid ?: $this->getOpenid();
        if (!$openid) {
            throw new Exception('openid不存在');
        }
        $out_trade_no = $out_trade_no ?: $this->getSnowflakeNumber("SK");
        $params = array(
            'body'           => $body ?: '默认商品',
            'out_trade_no'   => $out_trade_no,
            'total_fee'      => $total_fee,
            'trade_type'     => $trade_type,
            'openid'         => $openid,
            'attach'         => $attach,
            'profit_sharing' => $profit_sharing
        );
        try {
            $result = $this->getOrder()->unify($params);
            $WechatOrder = new WechatOrder();
            $order = $WechatOrder->where(['out_trade_no' => $out_trade_no])->find();
            if ($result['return_code'] === 'SUCCESS' && $result['result_code'] === 'SUCCESS' && !$order) {
                $order_data = array(
                    'body'         => $params['body'],
                    'out_trade_no' => $params['out_trade_no'],
                    'total_fee'    => $params['total_fee'],
                    'openid'       => $params['openid'],
                    'attach'       => $params['attach'],
                    'state'        => 0,
                    'is_share'     => $profit_sharing == "N" ? 0 : 1,
                    'share_state'  => 0,
                    'plaid'        => $this->plaid,
                    'addon'        => $this->addon_name
                );
                $WechatOrder->save($order_data);
            }
            $result['order_id'] = $WechatOrder->id;
            $result['out_trade_no'] = $params['out_trade_no'];
        } catch (\Exception $e) {
            Log::write($e->getMessage() . '出错行' . $e->getLine());
        }
        return $result;
    }

    /**
     * 订单查询
     * @param string $number 订单号
     * @param int $type 订单类型 商户订单号0，微信订单号1
     * @return array|false|string
     */
    public function orderQuery(string $number, int $type = 0)
    {
        if ($type === 0) {
            return $this->getOrder()->queryByOutTradeNumber($number);
        } elseif ($type === 1) {
            return $this->getOrder()->queryByTransactionId($number);
        }
        return false;
    }

    /**
     * 订单退款
     * @param string $number
     * @param string $refundMoney
     * @param string $refund_desc
     * @param string $totalMoney
     * @param string $refundNumber
     * @param array $config
     * @param int $type
     * @return array|\EasyWeChat\Kernel\Support\Collection|false|object|\Psr\Http\Message\ResponseInterface|string
     * @throws Exception
     * @throws InvalidConfigException
     */
    public function orderRefund(string $number, string $refundMoney, $refund_desc = '', string $totalMoney = '', string $refundNumber = '', array $config = [], int $type = 0)
    {
        //初始化退款单号
        $refundNumber = $refundNumber ?: $this->getSnowflakeNumber("TK");

        //订单金额如果没填默认为退款金额
        $totalMoney = $totalMoney ?: $refundMoney;

        $totalFee = intval($totalMoney * 100);
        $refundFee = intval($refundMoney * 100);
        if ($totalFee <= 0 || $refundFee <= 0) {
            throw new Exception('退款金额为空或者参数不正确');
        }
        $config = array_merge(['refund_desc' => $refund_desc], $config);
        if ($type === 0) {
            //商户号退款
            $result = $this->getOrderApp()->refund->byOutTradeNumber($number, $refundNumber, $totalFee, $refundFee, $config);
        } elseif ($type === 1) {
            //订单号退款
            $result = $this->getOrderApp()->refund->byTransactionId($number, $refundNumber, $totalFee, $refundFee, $config);
        } else {
            return false;
        }

        if ($this->checkResult($result)) {
            //如果退款成功，写入数据库
            $refund_data = array(
                'out_trade_no'   => $result['out_trade_no'],
                'transaction_id' => $result['transaction_id'],
                'out_refund_no'  => $result['out_refund_no'],
                'refund_id'      => $result['refund_id'],
                'refund_fee'     => $result['refund_fee'],
                'total_fee'      => $result['total_fee'],
                'refund_desc'    => $refund_desc,
                'plaid'          => $this->plaid,
                'addon'          => $this->addon_name
            );
            (new WechatRefund())->save($refund_data);
        }
        return $result;
    }

    /**
     * 创建分账接收方
     * @param string $account openid ||  mch_id或者sub_mch_id
     * @param string $relation_type https://pay.weixin.qq.com/wiki/doc/api/allocation.php?chapter=27_3&index=4
     * @param string $custom_relation 自定义的分账关系
     * @param string $type MERCHANT_ID商户号， PERSONAL_OPENID 个人
     * @param string $name 分账接收方全称 个人忽略
     * @return array
     */
    public function Receiver($account, $relation_type = "USER", $custom_relation = "", $type = "PERSONAL_OPENID", $name = "")
    {
        $receiver = [
            "type"            => $type,
            "account"         => $account,
            "name"            => $name,
            "relation_type"   => $relation_type,
            "custom_relation" => $custom_relation
        ];
        return $receiver;
    }

    /**
     * 添加分账接收方
     * @param $receiver
     * @return array
     */
    public function addReceiver($receiver)
    {
        $result = $this->getProfitSharing()->addReceiver($receiver);
        $this->handleReceiver($result);
        return $result;
    }

    /**
     * 删除分账接收方
     * @param $receiver
     * @return array
     */
    public function deleteReceiver($receiver)
    {
        $result = $this->getProfitSharing()->deleteReceiver($receiver);
        $this->handleReceiver($result, true);
        return $result;
    }

    /**
     * 单次分账
     * @param $transaction_id
     * @param $receivers
     * @param $out_order_no
     * @return array
     */
    public function share($transaction_id, $receivers, $out_order_no = "")
    {
        $WechatShare = new WechatShare();
        $share = $WechatShare->where(['transaction_id' => $transaction_id])->findOrEmpty();
        if ($share->isEmpty()) {
            $out_order_no = $out_order_no ?: $this->getSnowflakeNumber("FZ");
            $WechatShare->save(
                [
                    'transaction_id' => $transaction_id,
                    'out_order_no'   => $out_order_no,
                    'plaid'          => get_plaid(),
                    'receivers'      => $receivers
                ]
            );
        } else {
            $out_order_no = $out_order_no ?: $share['out_order_no'];
        }
        try {
            $result = $this->getProfitSharing()->share($transaction_id, $out_order_no, $receivers);
        } catch (\Exception $e) {
            Log::error('分账失败，检查配置和证书是否错误');
            return [];
        }
        $this->handleShare($result, $transaction_id);
        return $result;
    }

    /**
     * 创建一个分账任务
     * @param $receivers
     * @param $transaction_id
     * @param string $out_order_no
     * @param int $time_out
     * @return bool
     * @throws \think\db\exception\DataNotFoundException
     * @throws \think\db\exception\DbException
     * @throws \think\db\exception\ModelNotFoundException
     */
    public function createShareTask($receivers, $transaction_id, $out_order_no = "", $time_out = 0)
    {
        $pay = (new PlatformSetting())->getValueByKey("pay", $this->plaid);
        if ($time_out < 10) {
            $time_out = $pay['settlement_cycle_time'] ?? 10;
        }
        $order = (new WechatOrder())->where(['transaction_id' => $transaction_id])->find();
        if (!$order) {
            $this->err_msg = "订单不存在，无法创建";
            return false;
        }
        $share = WechatShare::where('transaction_id', $transaction_id)->findOrEmpty();
        if ($share->isEmpty()) {
            $plaid = get_plaid() ?: $order['plaid'];
            $out_order_no = $out_order_no ?: $this->getSnowflakeNumber("FZ");
            $data = array(
                'transaction_id' => $transaction_id,
                'out_order_no'   => $out_order_no,
                'status'         => '',
                'state'          => 0,
                'plaid'          => $plaid,
                'receivers'      => $receivers,
                'exec_time'      => time() + $time_out,
                'err_count'      => 0,
                'addon'          => $this->addon_name
            );
            return (new WechatShare())->save($data);
        } else {
            $this->err_msg = "分账任务已存在，无需创建";
            return false;
        }
    }

    /**
     * 分账给一个用户
     * @param $order_id int 订单ID
     * @param $openid string Opined
     * @param $amount int 金额（分）
     * @param $desc string 描述
     * @param string $relation_type
     * @return array|false
     */
    public function shareToUser($order_id, $openid, $amount, $desc, $relation_type = "USER")
    {
        $receiver = Ws::Receiver($openid, $relation_type);
        $this->addReceiver($receiver);
        $order = (new WechatOrder())->where(['id' => $order_id])->find();
        if (!$order) {
            return false;
        }
        $receivers = array(
            [
                "type"        => "PERSONAL_OPENID",
                "account"     => $openid,
                "amount"      => $amount,
                "description" => $desc
            ]
        );
        return $this->share($order['transaction_id'], $receivers);
    }

    /**
     * 多次分账 需配合多次分账完结
     * @param $transaction_id
     * @param $out_trade_no
     * @param $receivers
     * @return array
     */
    public function multiShare($transaction_id, $receivers, $out_order_no)
    {
        $out_order_no = $out_order_no ?: $this->getSnowflakeNumber("FZDC");
        return $this->getProfitSharing()->multiShare($transaction_id, $out_order_no, $receivers);
    }

    /**
     * 多次分账完结
     * @param $transaction_id
     * @param $out_trade_no
     * @param string $description
     * @return array
     */
    public function shareFinish($transaction_id, $description = "分账完结", $out_order_no = "")
    {
        $WechatShare = new WechatShare();
        $share = $WechatShare->where(['transaction_id' => $transaction_id])->findOrEmpty();
        if ($share->isEmpty()) {
            $out_order_no = $out_order_no ?: $this->getSnowflakeNumber("FZWJ");
            $WechatShare->save(
                [
                    'transaction_id' => $transaction_id,
                    'out_order_no'   => $out_order_no,
                    'plaid'          => get_plaid()
                ]
            );
        } else {
            $out_order_no = $out_order_no ?: $share['out_order_no'];
        }

        $result = $this->getProfitSharing()->markOrderAsFinished([
            "transaction_id" => $transaction_id,
            "out_order_no"   => $out_order_no,
            "description"    => $description
        ]);
        $this->handleShareFinish($result, $transaction_id);
        return $result;
    }

    /**
     * @param $result
     * @param $transaction_id
     * @return bool
     * @throws \think\db\exception\DataNotFoundException
     * @throws \think\db\exception\DbException
     * @throws \think\db\exception\ModelNotFoundException
     */
    protected function handleShareFinish($result, $transaction_id)
    {
        $WechatOrder = new WechatOrder();
        $WechatShare = new WechatShare();
        $order = $WechatOrder->where(['transaction_id' => $transaction_id, 'is_share' => 1])->find();
        if (!$order) {
            return false;
        }
        $share = $WechatShare->where(['transaction_id' => $transaction_id])->find();
        //         启动事务
        Db::startTrans();
        try {
            if ($result['return_code'] == "SUCCESS" && $result['result_code'] == "SUCCESS") {
                $res = $this->shareQuery($transaction_id, $result['out_order_no']);
                if ($res['return_code'] == "SUCCESS" && $res['result_code'] == "SUCCESS") {
                    $amount = $res['amount'];//分账的金额
                    $mch_id = $res['mch_id'];//商户号
                    $type = "MERCHANT_ID";
                    $WechatShareReceiver = new WechatShareReceiver();
                    $receiver_data = array(
                        'transaction_id' => $transaction_id,
                        'out_order_no'   => $result['out_order_no'],
                        'order_id'       => $result['order_id'],
                        'account'        => $mch_id,
                        'amount'         => $amount,
                        'description'    => $res['description'],
                        'detail_id'      => "",
                        'type'           => $type,
                        'result'         => "",
                        'plaid'          => get_plaid()
                    );
                    $WechatShareReceiver->save($receiver_data);
                    $share->receiver_count = 1;
                    $share->amount_count = $amount;
                    $share->out_order_no = $result['out_order_no'];
                    $share->order_id = $result['order_id'];
                    $share->state = 1;
                    $share->status = "FINISHED";
                    //订单
                    $order->share_state = 2;

                }
            } else {
                //分账
                $share->err_code = $result['err_code'] ?? 0;
                $share->err_code_des = $result['err_code_des'] ?? '';
                $share->state = -1;
                //订单
                $order->share_state = -1;
                $order->share_des = $result['err_code_des'] ?? '';
            }
            $order->save();
            $share->save();
            Db::commit();
            return true;
        } catch (\Exception $e) {
            // 回滚事务
            Log::error("执行函数handleShareFinish发生异常：" . $e->getMessage() . '出错行' . $e->getLine());
            Db::rollback();
            return false;
        }
    }


    /**
     * 分账结果处理
     */
    protected function handleShare($result, $transaction_id)
    {
        if (!is_array($result)) {
            return false;
        }
        $WechatOrder = new WechatOrder();
        $WechatShare = new WechatShare();
        $WechatShareReceiver = new WechatShareReceiver();
        $order = $WechatOrder->where(['transaction_id' => $transaction_id, 'is_share' => 1])->find();
        $share = $WechatShare->where(['transaction_id' => $transaction_id])->find();

        if (!$order || !$share) {
            Log::error("handleShare 分账：" . $transaction_id . "订单不存在或者分账不存在已删除");
            $share->delete();
            return false;
        }
//         启动事务
        Db::startTrans();
        try {
            if ($result['return_code'] == "SUCCESS" && $result["result_code"] == "SUCCESS") {
                //参与人
                $amount_count = 0;
                $receivers = json_decode($result['receivers'], true);
                foreach ($receivers as $key => $value) {
                    $receiver = $WechatShareReceiver->where(['detail_id' => $value['detail_id']])->findOrEmpty();
                    if ($receiver->isEmpty()) {
                        $receiver_data = array(
                            'transaction_id' => $transaction_id,
                            'out_order_no'   => $result['out_order_no'],
                            'order_id'       => $result['order_id'],
                            'account'        => $value['account'],
                            'amount'         => $value['amount'],
                            'description'    => $value['description'],
                            'detail_id'      => $value['detail_id'],
                            'type'           => $value['type'],
                            'result'         => $value['result'],
                            'plaid'          => get_plaid()
                        );
                        $amount_count += $value['amount'];
                        $receiver->save($receiver_data);
                    } else {
                        $receiver->result = $value['result'];
                        $receiver->save();
                    }
                }
                //分账
                $share->receiver_count = count($receivers);
                $share->amount_count = $amount_count;
                $share->out_order_no = $result['out_order_no'];
                $share->order_id = $result['order_id'];
                $share->state = 1;
                $share->status = $result['status'];
                $share->err_code_des = "OK";
                //订单
                $order->share_state = 2;
            } else {
                //分账
                $share->err_code = $result['err_code'] ?? 0;
                if ($result['return_code'] == 'FAIL') {
                    $share->err_code_des = $result['return_msg'] ?? '';
                } else {
                    $share->err_code_des = $result['err_code_des'] ?? '';
                }
                $share->state = -1;
                $share->err_count = $share['err_count'] + 1;
                //订单
                $order->share_state = -1;
                $order->share_des = $result['err_code_des'] ?? '';
            }
            $order->save();
            $share->save();
            Db::commit();
            return true;
        } catch (\Exception $e) {
            // 回滚事务
            Log::error("执行函数handleShare发生异常：" . $e->getMessage() . '出错行' . $e->getLine());
            Db::rollback();
            return false;
        }
    }

    /**
     * 处理用户请求结果
     * @param $result
     * @param boolean $is_del
     */
    protected function handleReceiver($result, $is_del = false)
    {
        if (is_array($result)) {
            if ($result['return_code'] == "SUCCESS" && $result["result_code"] == "SUCCESS") {
                $receiver = json_decode($result['receiver'], true);
                if ($receiver['type'] == 'PERSONAL_OPENID') {
                    $user = (new WechatUser())->where(['openid' => $receiver['account']])->find();
                    if ($is_del) {
                        $user->relation_type = "";
                        $user->save();
                    } else if ($user && !$user['relation_type']) {
                        if ($receiver['relation_type'] == "CUSTOM") {
                            $receiver['relation_type'] = $receiver["custom_relation"];
                        }
                        $user->relation_type = $receiver['relation_type'];
                        $user->save();
                    }
                }
            }
        }
    }

    /**
     * 查询分账
     * @param $transaction_id
     * @param $out_order_no
     * @return array|\EasyWeChat\Kernel\Support\Collection|object|\Psr\Http\Message\ResponseInterface|string
     */
    public function shareQuery($transaction_id, $out_order_no)
    {
        return $this->getProfitSharing()->query($transaction_id, $out_order_no);
    }

    /**
     * @param string $number 订单号 默认为商户退款订单号
     * @param int $type 0 商户退款订单号 1 微信退款订单号 2 商户订单号 3 微信订单号
     */
    public function orderRefundQuery($number, $type = 0)
    {
        switch ($type) {
            case 0:
                //商户退款订单号
                return $this->orderApp->refund->queryByOutRefundNumber($number);
            case 1:
                //微信退款订单号
                return $this->orderApp->refund->queryByRefundId($number);
            case 2:
                //商户订单号
                return $this->orderApp->refund->queryByOutTradeNumber($number);
            case 3:
                //微信订单号
                return $this->orderApp->refund->queryByTransactionId($number);
            default:
                return false;
        }
    }

    /**
     * 获取支付配置
     * @param $prepayId
     * @param string $type
     * @return array|false|string
     */
    public function getOrderJssdk($prepayId, $type = 'JSSDK')
    {
        $jssdk = $this->orderApp->jssdk;
        if ($type === 'WeixinJSBridge') {
            return $jssdk->bridgeConfig($prepayId);
        } elseif ($type === 'JSSDK') {
            return $jssdk->sdkConfig($prepayId);
        } elseif ($type === 'WxApp') {
            return $jssdk->bridgeConfig($prepayId, false);
        }
        return false;
    }

    /**
     * 获取支付结果通知地址
     * @return string
     */
    protected function getNotifyUrl()
    {
        return url('notify', ['plaid' => $this->plaid, 'addon' => $this->addon_name])->domain(true)->build();
    }

    /**
     * 获取雪花订单号
     * @param string $prefix 前缀，默认SK收款，TK退款，FK付款、FZ分账
     * @return string
     */
    public function getSnowflakeNumber($prefix = 'SK')
    {
        $id = Snowflake::id();
        $id = substr($id, 4);
        $ip_num = '';
        foreach (explode('.', request()->ip()) as $key => $val) {
            if ($val == 0) {
                $ip_num .= '000';
            } elseif ($val < 10) {
                $ip_num .= '00' . $val;
            } elseif ($val < 100) {
                $ip_num .= '0' . $val;
            } else {
                $ip_num .= $val;
            }
        }
        $number = substr($prefix, 0, 6) . date('Ymd', time()) . $id;
        return $number;
    }

    /**
     * 检查返回值
     * @param $result
     * @return bool
     */
    public function checkResult($result)
    {
        if ($result['return_code'] === 'SUCCESS' && $result['result_code'] === 'SUCCESS') {
            return true;
        } else {
            return false;
        }
    }

    /**
     * 设置企付零配置
     * @param array $transferConfig
     */
    public function setTransferConfig(array $transferConfig): void
    {
        $this->transferConfig = $transferConfig;
    }

    /**
     * 置支付配置
     * @param array $orderConfig
     */
    public function setOrderConfig(array $orderConfig): void
    {
        $this->orderConfig = $orderConfig;
    }
}
